import { tablePageConfig, tableProxyConfig } from '../config'

import _at from 'lodash/at'
import _set from 'lodash/set'
import _merge from 'lodash/merge'

export default {
  data() {
    return {
      pageInfo: {},
      _tableParams: {}
    }
  },
  props: {
    requestMethod: {
      type: Function,
      default: null
    },
    tableParams: {
      type: Object,
      default() {
        return {}
      }
    },
    remoteSort: {
      type: Boolean,
      default: true
    }
  },
  watch: {
    // TODO: 是否可以通过外面规范传参来避免这个 watch?
    tableParams: {
      handler(newVal, oldVal) {
        this._tableParams = {
          // 外面的tableParams 直接赋值即可，但是还是需要考虑上方的todo
          ...this._tableParams,
          ...oldVal,
          ...newVal
        }
      },
      immediate: true,
      deep: true
    }
  },
  computed: {
    /**
     * @returns {import('vxe-table').GridProxyConfig}
     */
    proxyConfig() {
      const { 'proxy-config': proxyConfig } = this.$attrs
      if (!this.requestMethod && !proxyConfig) return null

      /** @type {import('vxe-table').GridProxyConfig} */
      const config = {
        sort: true,
        ajax: {
          query: (...args) => {
            const [originArgs, ...otherArgs] = args
            _merge(originArgs, ...otherArgs)
            const params = {}
            const { page, sort } = originArgs
            const { order, property, sortBy } = sort
            params.SortOrder = order?.toUpperCase() || ''
            params.SortField = sortBy || property || ''
            if (page) {
              params.pageNum = page.currentPage
              params.pageSize = page.pageSize
            }
            // 记录请求的参数
            Object.assign(this.pageInfo, params)
            return this.$requestMethod({
              ...params,
              ...this._tableParams
            })
          }
        }
      }
      return Object.assign({}, tableProxyConfig, proxyConfig, config)
    },
    tablePage() {
      const { 'pager-config': pagerConfig } = this.$attrs
      if (!pagerConfig && !this.proxyConfig) return null
      return _merge({}, tablePageConfig, pagerConfig, {
        pageSize: this.pageInfo.pageSize,
        pageNum: this.pageInfo.pageNum
      })
    },
    /** @return {import('vxe-table').TableSortConfig} */
    sortConfig() {
      return {
        remote: this.remoteSort
      }
    }
  },
  methods: {
    async $requestMethod(params) {
      const data = await this.requestMethod(params)
      _set(
        data,
        this.proxyConfig.props.total,
        Number(_at(data, this.proxyConfig.props.total)) ?? 0
      )
      return data
    },
    loadTableData(tableData) {
      this._loadData(tableData)
    },
    /**
     * @param {Boolean} keepCurrentPage
     */
    refreshTable(keepCurrentPage = false) {
      const pageConfig = {}
      if (!keepCurrentPage) {
        pageConfig.page = {
          currentPage: 1
        }
        this.pageInfo.PageIndex = 1
      }
      // ensure props data has been updated
      this.$nextTick(() => {
        this._commitProxy('query', pageConfig)
      })
    },
    reloadTable() {
      this._commitProxy('reload')
    }
  }
}
